﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using WorkFlowCore.Conditions;
using WorkFlowCore.EventData;
using WorkFlowCore.IRepositories;
using WorkFlowCore.Workflows;
using WorkFlowCore.WorkTasks;
using Volo.Abp.Uow;
using Volo.Abp.EventBus.Local;
using Volo.Abp.Domain.Services;
using System.Text.RegularExpressions;
using Volo.Abp.EventBus.Distributed;
using WorkFlowCore.UserSelectors;

namespace WorkFlowCore.WorkTasks
{
    public class WorkTaskManager : IDomainService
    {
        private readonly IBasicRepository<Workflow, Guid> workflowRepository;
        private readonly IBasicRepository<WorkflowVersionInfo, Guid> versionRepository;
        private readonly IWorkTaskRepository workTaskRepository;
        private readonly IWorkStepRepository workStepRepository;
        private readonly ConditionManager conditionManager;
        private readonly UserSelectorManager userSelectorManager;
        private readonly ILocalEventBus eventManager;
        private readonly IUnitOfWorkManager unitOfWorkManager;
        private readonly WorkflowStore workflowStore;
        private readonly IDistributedEventBus distributedEventBus;

        public WorkTaskManager(IBasicRepository<Workflow, Guid> workflowRepository, IBasicRepository<WorkflowVersionInfo, Guid> versionRepository, IWorkTaskRepository workTaskRepository, IWorkStepRepository workStepRepository, ConditionManager conditionManager, UserSelectorManager userSelectorManager, ILocalEventBus eventManager, IUnitOfWorkManager unitOfWorkManager, WorkflowStore workflowStore, IDistributedEventBus distributedEventBus)
        {
            this.workflowRepository = workflowRepository;
            this.versionRepository = versionRepository;
            this.workTaskRepository = workTaskRepository;
            this.workStepRepository = workStepRepository;
            this.conditionManager = conditionManager;
            this.userSelectorManager = userSelectorManager;
            this.eventManager = eventManager;
            this.unitOfWorkManager = unitOfWorkManager;
            this.workflowStore = workflowStore;
            this.distributedEventBus = distributedEventBus;
        }


        #region 流程审批操作

        /// <summary>
        /// 创建流程
        /// </summary>
        /// <param name="workflowId"></param>
        /// <param name="name"></param>
        /// <param name="formData"></param>
        /// <param name="entityFullName"></param>
        /// <param name="entityKeyValue"></param>
        /// <returns></returns>
        public async Task<WorkTask> CreateWorkTask(WorkflowId workflowId, string name, string formData, string entityFullName, string entityKeyValue, string createdUserId)
        {

            var worktaskInfo = await workTaskRepository.GetAsync(w => w.EntityFullName == entityFullName && w.EntityKeyValue == entityKeyValue && w.WorkflowId_Id == workflowId.Id && w.WorkflowId_VersionId == workflowId.VersionId);

            if (worktaskInfo == null)
            {
                var worktask = new WorkTask(Guid.NewGuid(), workflowId, name, formData, entityFullName, entityKeyValue, createdUserId);
                worktaskInfo = worktask.ToWorkTaskInfo();
                using (var unitOfWork = unitOfWorkManager.Begin())
                {
                    await workTaskRepository.InsertAsync(worktaskInfo);
                    await unitOfWork.CompleteAsync();
                }
            }
            return worktaskInfo.ToWorkTask();
        }

        /// <summary>
        /// 创建模拟流程
        /// </summary>
        /// <param name="workflowId"></param>
        /// <param name="name"></param>
        /// <param name="formData"></param>
        /// <param name="entityFullName"></param>
        /// <param name="entityKeyValue"></param>
        /// <returns></returns>
        public async Task<WorkTask> CreateSimulationWorkTask(WorkflowId workflowId, string name, string formData, string entityFullName, string entityKeyValue, string createdUserId)
        {

            var worktask = new WorkTask(Guid.NewGuid(), workflowId, name, formData, entityFullName, entityKeyValue, createdUserId);
            worktask.AsSimulation();
            using (var unitOfWork = unitOfWorkManager.Begin())
            {
                await workTaskRepository.InsertAsync(worktask.ToWorkTaskInfo());
                await unitOfWork.CompleteAsync();
            }
            return worktask;
        }


        private async Task<WorkflowNode> GetNodeByWorkflowIdAndNodeId(WorkflowVersion workflowVersion, WorkflowId workflowId, Guid nodeId)
        {
            //workflowVersion = await workflowStore.GetWorkflowVersion(workflowId.Id, workflowId.VersionId);
            return workflowVersion.AllNodes.FirstOrDefault(n => n.Id == nodeId);
        }


        /// <summary>
        /// 获取审批的下一步节点
        /// </summary>
        /// <param name="node"></param>
        /// <param name="workTask"></param>
        /// <returns></returns>
        private async Task<List<WorkflowNode>> GetNextNodes(WorkflowVersion workflowVersion, WorkflowNode node, WorkTask workTask, WorkStep cuttentWorkStep)
        {
            var nodes = new List<WorkflowNode>();

            //var workflowVersion = await workflowStore.GetWorkflowVersion(workTask.WorkflowId.Id, workTask.WorkflowId.VersionId);
            //普通节点的下组节点要排除掉 子流程节点
            var toNodeLines = workflowVersion.NodeMaps.Where(n => n.FromNode.Id == node.Id && n.MapType == NodeMap.NodeMapType.Normal && n.ToNode.NodeType != WorkNodeType.SubNode);

            foreach (var line in toNodeLines)
            {
                if (line.CanAccept(workTask, cuttentWorkStep, conditionManager))
                {
                    var tonode = line.ToNode;
                    nodes.Add(tonode);
                }
            }
            return nodes;
        }

        /// <summary>
        /// 获取审批的下一步节点
        /// </summary>
        /// <param name="node"></param>
        /// <param name="workTask"></param>
        /// <returns></returns>
        private async Task<List<WorkflowNode>> GetNextNodesOfSubProcess(WorkflowVersion workflowVersion, WorkflowNode node, WorkTask workTask, WorkStep cuttentWorkStep)
        {
            var nodes = new List<WorkflowNode>();

            //var workflowVersion = await workflowStore.GetWorkflowVersion(workTask.WorkflowId.Id, workTask.WorkflowId.VersionId);

            //只查子流程节点
            var toNodeLines = workflowVersion.NodeMaps.Where(n => n.FromNode.Id == node.Id && n.MapType == NodeMap.NodeMapType.Normal && n.ToNode.NodeType == WorkNodeType.SubNode);

            foreach (var line in toNodeLines)
            {
                if (line.CanAccept(workTask, cuttentWorkStep, conditionManager))
                {
                    var tonode = line.ToNode;
                    nodes.Add(tonode);
                }
            }
            return nodes;
        }

        /// <summary>
        /// 
        /// </summary>
        /// <param name="node"></param>
        /// <param name="workTask"></param>
        /// <param name="currentWorkStep"></param>
        /// <param name="rejectToNodeId">指定的节点：如果由前台指定了驳回的id，则这里将只获取指定的节点</param>
        /// <returns></returns>
        private async Task<Tuple<List<WorkStep>, List<WorkflowNode>>> GetRejectInfo(WorkflowVersion workflowVersion, WorkflowNode node, WorkTask workTask, WorkStep currentWorkStep, Guid? rejectToNodeId = null)
        {
            /*
             * 如果指定了拒绝返回的节点，则按指定节点返回
             * 如果没指定返回节点，则判断来源节点是不是拒绝步骤，
             *  是   根据流程节点关系推断退回节点
             *  否   根据审批记录退回到上一个节点
             */


            //var workflowVersion = await workflowStore.GetWorkflowVersion(workTask.WorkflowId.Id, workTask.WorkflowId.VersionId);
            var preSteps = (await workStepRepository.GetListAsync(ws => ws.GroupId == currentWorkStep.PreStepGroupId)).Select(s => s.ToWorkStep()).ToList();

            //按节点和审批人员取最新的审批记录
            preSteps = preSteps.GroupBy(s => s.NodeId + s.HandleUser.ToString()).Select(g => g.OrderByDescending(step => step.CreationTime).First()).ToList();

            var rejectNodes = new List<WorkflowNode>();
            var groupId = Guid.NewGuid().ToString();
            var steps = new List<WorkStep>();

            if (rejectToNodeId != null && rejectToNodeId != Guid.Empty)
            {
                var toNode = workflowVersion.AllNodes.FirstOrDefault(n => n.Id == rejectToNodeId);
                rejectNodes.Add(toNode);
                steps.AddRange(GetApproveSteps(currentWorkStep.NodeId, node.Name, workTask, toNode, currentWorkStep.GroupId, groupId));
            }
            else if (node.RejectNodes != null && node.RejectNodes.Any())
            {
                //如果指定了回滚的节点，则按指定节点回滚
                foreach (var rejectNode in node.RejectNodes)
                {
                    var toNode = workflowVersion.AllNodes.FirstOrDefault(n => n.Id == rejectNode.NodeId);
                    rejectNodes.Add(toNode);
                    steps.AddRange(GetApproveSteps(currentWorkStep.NodeId, node.Name, workTask, toNode, currentWorkStep.GroupId, groupId));
                }
            }
            else if (preSteps.Where(ps => ps.HandleType == WorkStepHandleType.Reject).Any())
            {
                var toNodeLines = workflowVersion.NodeMaps.Where(n => n.FromNode.Id == node.Id && n.MapType == NodeMap.NodeMapType.Reject);

                foreach (var line in toNodeLines)
                {
                    if (line.CanAccept(workTask, currentWorkStep, conditionManager))
                    {
                        var toNode = line.ToNode;
                        rejectNodes.Add(toNode);
                        steps.AddRange(GetApproveSteps(currentWorkStep.NodeId, node.Name, workTask, toNode, currentWorkStep.GroupId, groupId));
                    }
                }
            }
            else
            {

                preSteps.ForEach(st =>
                {
                    var toNode = workflowVersion.AllNodes.FirstOrDefault(n => n.Id == st.NodeId);
                    rejectNodes.Add(toNode);
                    steps.Add(st.Copy(groupId));

                });
            }



            return Tuple.Create(steps, rejectNodes);
        }


        /// <summary>
        /// 
        /// </summary>
        /// <param name="node"></param>
        /// <param name="workTask"></param>
        /// <param name="currentWorkStep"></param>
        /// <returns></returns>
        private async Task<List<WorkflowNode>> GetRejectNodes(WorkflowVersion workflowVersion, WorkflowNode node, WorkTask workTask, WorkStep currentWorkStep)
        {
            /*
             *  判断来源节点是不是拒绝步骤，
             *  是   根据流程节点关系推断退回节点
             *  否   根据审批记录退回到上一个节点
             */


            //var workflowVersion = await workflowStore.GetWorkflowVersion(workTask.WorkflowId.Id, workTask.WorkflowId.VersionId);
            var preSteps = (await workStepRepository.GetListAsync(ws => ws.GroupId == currentWorkStep.PreStepGroupId)).Select(s => s.ToWorkStep()).ToList();

            //按节点和审批人员取最新的审批记录
            preSteps = preSteps.GroupBy(s => s.NodeId + s.HandleUser.ToString()).Select(g => g.OrderByDescending(step => step.CreationTime).First()).ToList();

            var rejectNodes = new List<WorkflowNode>();

            if (preSteps.Where(ps => ps.HandleType == WorkStepHandleType.Reject).Any())
            {
                var toNodeLines = workflowVersion.NodeMaps.Where(n => n.FromNode.Id == node.Id && n.MapType == NodeMap.NodeMapType.Reject);

                foreach (var line in toNodeLines)
                {
                    if (line.CanAccept(workTask, currentWorkStep, conditionManager))
                    {
                        var toNode = line.ToNode;

                        rejectNodes.Add(toNode);
                    }
                }
            }
            else
            {

                preSteps.ForEach(st =>
                {
                    var toNode = workflowVersion.AllNodes.FirstOrDefault(n => n.Id == st.NodeId);

                    rejectNodes.Add(toNode);

                });
            }
            return rejectNodes;
        }



        /// <summary>
        /// 获取节点派发的成员
        /// </summary>
        /// <param name="node"></param>
        /// <param name="workTask"></param>
        /// <returns></returns>
        public Dictionary<NodeUser.NodeHandleType, List<User>> GetNodeUsers(WorkflowNode node, WorkTask workTask)
        {
            return node.GetHandleUsers(workTask, userSelectorManager);
        }


        /// <summary>
        /// 更新同组其它审批步骤状态为未处理
        /// </summary>
        /// <param name="currentNodeId"></param>
        /// <param name="stepGroupId"></param>
        /// <returns></returns>
        private async Task UpdateOtherStepsStatusWithUnWork(Guid currentNodeId, string stepGroupId)
        {
            await Task.CompletedTask;
            var stepInfos = new List<WorkStepInfo>();
            //更新步骤所包含的节点状态为 未处理状态
            var steps = await workStepRepository.GetListAsync(s => s.NodeId != currentNodeId && s.GroupId == stepGroupId);
            foreach (var stepInfo in steps)
            {
                //对于未处理的记录，更新其处理状态
                if (!stepInfo.IsHandled)
                {
                    var step = stepInfo.ToWorkStep();
                    step.Handle(WorkStepHandleType.UnWork);
                    stepInfos.Add(step.ToWorkStepInfo(stepInfo));
                }
            }
            using (var unitOfWork = unitOfWorkManager.Begin())
            {
                await workStepRepository.UpdateManyAsync(stepInfos);
                await unitOfWork.CompleteAsync();
            }
        }
        /// <summary>
        /// 更新同节点其它用户步骤状态为未处理
        /// 更新当前步骤所在节点的其它审批步骤为  未处理 状态
        /// </summary>
        /// <param name="currentWorkStep"></param>
        /// <returns></returns>
        private async Task UpdateOtherStepsStatusWithUnWorkOfNode(WorkStep currentWorkStep)
        {
            await Task.CompletedTask;
            var stepInfos = new List<WorkStepInfo>();
            var steps = await workStepRepository.GetListAsync(ws => ws.NodeId == currentWorkStep.NodeId && ws.GroupId == currentWorkStep.GroupId && ws.Id != currentWorkStep.Id && !ws.IsHandled);
            foreach (var stepInfo in steps)
            {
                //对于未处理的记录，更新其处理状态
                if (!stepInfo.IsHandled)
                {
                    var step = stepInfo.ToWorkStep();
                    step.Handle(WorkStepHandleType.UnWork);
                    stepInfos.Add(step.ToWorkStepInfo(stepInfo));
                }
            }
            await workStepRepository.UpdateManyAsync(stepInfos);
        }




        /// <summary>
        /// 发起审批
        /// </summary>
        /// <param name="workTaskId"></param>
        /// <returns></returns>
        public async Task<List<WorkStep>> WorkTaskStart(Guid workTaskId)
        {
            var workTaskInfo = await workTaskRepository.GetAsync(workTaskId);
            if (workTaskInfo == null) return new List<WorkStep>();
            var workTask = workTaskInfo.ToWorkTask();
            if (!workTask.IsPending) return new List<WorkStep>();
            workTask.SetProcessing();
            var workflowVersion = await workflowStore.GetWorkflowVersion(workTask.WorkflowId.Id, workTask.WorkflowId.VersionId);
            if(workflowVersion==null|| workflowVersion.NodeMaps==null|| workflowVersion.NodeMaps.Count() == 0)
            {
                throw new Exception("发起失败，流程设计无效！");
            }
            var startNode = workflowVersion.NodeMaps.FirstOrDefault(n => n.FromNode.NodeType == WorkNodeType.Begin)?.FromNode;

            var steps = GetApproveSteps(Guid.Empty, "", workTask, startNode, string.Empty, Guid.NewGuid().ToString());
            using (var unitOfWork = unitOfWorkManager.Begin())
            {
                await workTaskRepository.UpdateAsync(workTask.ToWorkTaskInfo(workTaskInfo));
                steps.ForEach(step => step.SetFormData(workTask.FormData));
                await SendTasks(workTask, steps);
                await unitOfWork.CompleteAsync();
            }

            //自动处理开始节点


            await eventManager.PublishAsync(new TaskStateChangeEventData
            {
                WorkTask = workTask,
                OldWorkTaskStatus = WorkTaskStatus.Pending,
                NewWorkTaskStatus = workTask.WorkTaskStatus,
            });
            await eventManager.PublishAsync(new AutoHandleStepsEventData() { Steps = steps, Comment = "发起审批" });

            return steps;
        }

        /// <summary>
        /// 判断当前节点所有人员是否都处理完了
        /// </summary>
        /// <param name="currentWorkStep"></param>
        /// <param name="workTask"></param>
        /// <returns></returns>
        private async Task<bool> HasAllHandlersWorkflowed(WorkStep currentWorkStep, WorkTask workTask)
        {
            await Task.CompletedTask;
            var GetCountAsync = await workStepRepository.GetCountAsync(ws => ws.GroupId == currentWorkStep.GroupId && ws.Id != currentWorkStep.Id && !ws.IsHandled);
            return GetCountAsync == 0;
        }

        /// <summary>
        /// 通过审批
        /// </summary>
        /// <param name="workStepId"></param>
        /// <param name="comment"></param>
        /// <param name="resourceIds"></param>
        /// <param name="formData"></param>
        /// <param name="userSelectors"></param>
        /// <returns></returns>
        public async Task<ProveResult> PassApprove(Guid workStepId, string comment = null, string resourceIds = null, string formData = null, List<NodeUser> userSelectors = null)
        {
            var currentWorkStepInfo = await workStepRepository.GetAsync(workStepId);
            var currentWorkStep = currentWorkStepInfo.ToWorkStep();

            if (currentWorkStep.WorkStepType == WorkStepType.ReadOnly)
                return ProveResult.Failed("只读步骤无法处理！");

            if (currentWorkStep.IsHandled && currentWorkStep.HandleType != WorkStepHandleType.Processing)
                return ProveResult.Failed("步骤已处理！");

            //派发下个节点任务
            var workTaskInfo = await workTaskRepository.GetAsync(currentWorkStep.WorkTaskId);
            var workTask = workTaskInfo.ToWorkTask();

            if (workTask.IsProcessed)
                return ProveResult.Failed("流程已审批！");

            var workflowVersion = await workflowStore.GetWorkflowVersion(workTask.WorkflowId.Id, workTask.WorkflowId.VersionId);
            var currentNode = await GetNodeByWorkflowIdAndNodeId(workflowVersion, workTask.WorkflowId, currentWorkStep.NodeId);
            var steps = new List<WorkStep>();
            var stepsOfSubProcess = new List<WorkStep>();
            var stepsOfSubNode = new List<WorkStep>();

            //在根据条件获取下一组审批步骤之前，先指定当前的审批表单（当前提交的），以便从更多维度决定下一组处理的节点
            currentWorkStep.SetFormData(formData);

            List<WorkflowNode> nextNodes = null;
            //如果当前审批节点是子流程，：如果不是处理中（没走子流程），则先走子流程，并改状态为处理中，否则，改为完成
            if (currentNode.NodeType == WorkNodeType.SubProcess && !currentWorkStep.IsHandled)
            {
                nextNodes = await GetNextNodesOfSubProcess(workflowVersion, currentNode, workTask, currentWorkStep);
                currentWorkStep.Handle(WorkStepHandleType.Processing, comment, resourceIds);
            }
            else
            {
                nextNodes = await GetNextNodes(workflowVersion, currentNode, workTask, currentWorkStep);
                currentWorkStep.Handle(WorkStepHandleType.Pass, comment, resourceIds);
            }

            if (currentNode.IsWaitingAllUser)
            {
                lock ("WorkNodeType.Sign")
                {
                    if (!HasAllHandlersWorkflowed(currentWorkStep, workTask).Result)
                    {
                        //更新当前处理节点为已处理
                        using (var unitOfWork = unitOfWorkManager.Begin())
                        {
                            workStepRepository.UpdateAsync(currentWorkStep.ToWorkStepInfo(currentWorkStepInfo)).Wait();
                            unitOfWork.Commit();
                        }
                        return ProveResult.Succeed(steps);
                    }
                }
            }
            else
            {
                await UpdateOtherStepsStatusWithUnWorkOfNode(currentWorkStep);
            }

            if (nextNodes.Count == 1)
            {
                //如果是会签操作,则确保所有会签中的操作都完成了才进行下一步
                if (nextNodes[0].NodeType == WorkNodeType.Sign)
                {
                    //会签
                    //等待所有待处理的处理才继续
                    lock ("WorkNodeType.Sign")
                    {
                        if (GetOnHandingSignStepsCount(currentWorkStep.NodeId, currentWorkStep.GroupId).Result != 0)
                        {
                            //更新当前处理节点为已处理
                            using (var unitOfWork = unitOfWorkManager.Begin())
                            {
                                workStepRepository.UpdateAsync(currentWorkStep.ToWorkStepInfo(currentWorkStepInfo)).Wait();
                                unitOfWork.Commit();
                            }
                            //自动处理同级其它审批步骤
                            AutoHandleSameGroupOfUser(currentWorkStep.Id, currentWorkStep.HandleUser, currentWorkStep.GroupId).Wait();

                            return ProveResult.Succeed(steps); ;
                        }
                    }
                }
                //如果子流程走完回到
                else if (nextNodes[0].NodeType == WorkNodeType.SubProcess)
                {
                    if (nextNodes[0].Id == currentWorkStep.SubProcessNode?.NodeId)
                    {
                        var step = (await workStepRepository.GetAsync(currentWorkStep.SubProcessNode.WorkStepId)).ToWorkStep();
                        stepsOfSubNode.Add(step);
                        nextNodes.Clear();
                    }
                }
            }
            var nextGroupId = Guid.NewGuid().ToString();

            foreach (var node in nextNodes)
            {
                //如果是子流程节点，无需指定审批人员
                if (node.NodeType == WorkNodeType.SubProcess)
                {
                    var step = new WorkStep(Guid.NewGuid(), workTask.Id, currentWorkStep.NodeId, currentNode.Name, node.Id, node.Name, null, WorkStepType.Auto, currentWorkStep.GroupId, nextGroupId);
                    stepsOfSubProcess.Add(step);
                    continue;
                }
                //如果 指定了处理人，则直接派给处理人
                //如果指定了 抄送（只读）人员，直接推送给抄送人员
                if (userSelectors != null && userSelectors.Any())
                {
                    GetUsersByUserSelectors(userSelectors, null, (selector, user) =>
                    {
                        steps.Add(new WorkStep(Guid.NewGuid(), workTask.Id, currentWorkStep.NodeId, currentNode.Name, node.Id, node.Name, new User
                        {
                            Id = user.Id,
                            Name = user.Name
                        }, selector.HandleType == NodeUser.NodeHandleType.Handle ? WorkStepType.Handle : WorkStepType.ReadOnly, currentWorkStep.GroupId, nextGroupId));
                    });
                }
                else
                {
                    steps.AddRange(GetApproveSteps(currentWorkStep.NodeId, currentNode.Name, workTask, node, currentWorkStep.GroupId, nextGroupId));
                }
            }



            if (!steps.Any() && !stepsOfSubProcess.Any() && !stepsOfSubNode.Any() && currentNode.NodeType != WorkNodeType.End)
                return ProveResult.Failed("找不到可以处理的下一个步骤！");

            //如果是子流程节点，子流程信息要传递下去
            if (currentNode.NodeType == WorkNodeType.SubProcess && currentWorkStep.HandleType == WorkStepHandleType.Processing)
            {
                steps.ForEach(s => s.Work4SubProcess(new SubProcessNode(currentNode.Id, currentWorkStep.Id)));
            }
            else if (currentWorkStep.SubProcessNode != null)
            {
                steps.ForEach(s => s.Work4SubProcess(currentWorkStep.SubProcessNode));
            }

            //更新当前处理节点为已处理
            using (var unitOfWork = unitOfWorkManager.Begin())
            {
                workStepRepository.UpdateAsync(currentWorkStep.ToWorkStepInfo(currentWorkStepInfo)).Wait();
                await SendTasks(workTask, steps);
                
                await SendTasks(workTask, stepsOfSubProcess);
               
                if (!unitOfWork.Commit())
                {
                    return ProveResult.Failed("提交失败");
                }

                //检查更新流程状态为审判中或者结束
                await CheckAndSetTaskProcessing(workTask, workTaskInfo, currentNode);
                await CheckAndSetTaskProcessed(workTask, workTaskInfo, currentNode);
                //子流程步骤自动处理
                if (stepsOfSubProcess.Any())
                    await eventManager.PublishAsync(new AutoHandleStepsEventData() { Steps = stepsOfSubProcess, Comment = "子流程自动处理" });

                if (stepsOfSubNode.Any())
                    await eventManager.PublishAsync(new AutoHandleStepsEventData() { Steps = stepsOfSubNode, Comment = "子流程自动处理" });
            }

           
            //自动处理结束节点
            if (nextNodes.Count == 1 && nextNodes[0].NodeType == WorkNodeType.End)
            {
                await eventManager.PublishAsync(new AutoHandleStepsEventData() { Steps = steps, Comment = "审批结束" });
            }

            await AutoHandleNextGroupOfUser(workflowVersion, steps, currentWorkStep.HandleUser);
            await AutoHandleNextGroupOfUser(workflowVersion, stepsOfSubProcess, currentWorkStep.HandleUser);

            //自动处理同级其它审批步骤
            await AutoHandleSameGroupOfUser(currentWorkStep.Id, currentWorkStep.HandleUser, currentWorkStep.GroupId);

            return ProveResult.Succeed(steps);
        }

        /// <summary>
        /// 驳回审批
        /// </summary>
        /// <returns></returns>
        public async Task<ProveResult> RejectApprove(Guid workStepId, string comment = null, string resourceIds = null, string formData = null, Guid? rejectToNodeId = null)
        {
            var currentWorkStepInfo = await workStepRepository.GetAsync(workStepId);
            var currentWorkStep = currentWorkStepInfo.ToWorkStep();

            if (currentWorkStep.WorkStepType == WorkStepType.ReadOnly)
                return ProveResult.Failed("只读步骤无法处理！");

            if (currentWorkStep.IsHandled)
                return ProveResult.Failed("步骤已处理！");


            var workTaskInfo = await workTaskRepository.GetAsync(currentWorkStep.WorkTaskId);
            var workTask = workTaskInfo.ToWorkTask();

            if (workTask.IsProcessed)
                return ProveResult.Failed("流程已审批！");

            var oldWorkTaskStatus = workTask.WorkTaskStatus;
            var workflowVersion = await workflowStore.GetWorkflowVersion(workTask.WorkflowId.Id, workTask.WorkflowId.VersionId);
            //将任务驳回上一步骤
            var currentNode = await GetNodeByWorkflowIdAndNodeId(workflowVersion, workTask.WorkflowId, currentWorkStep.NodeId);

            if (currentNode.NodeType == WorkNodeType.Begin)
                return ProveResult.Failed("开始步骤无法拒绝！");


            //TODO 子流程节点会自动往上一层驳回

            //更新当前处理节点为已处理
            using (var unitOfWork = unitOfWorkManager.Begin())
            {
                currentWorkStep.Handle(WorkStepHandleType.Reject, comment, resourceIds);
                await workStepRepository.UpdateAsync(currentWorkStep.ToWorkStepInfo(currentWorkStepInfo));
                var steps = new List<WorkStep>();

                //在根据条件获取下一组审批步骤之前，先指定当前的审批表单（当前提交的），以便从更多维度决定下一组处理的节点
                currentWorkStep.SetFormData(formData);

                var nextNodes = await GetNextNodes(workflowVersion, currentNode, workTask, currentWorkStep);
                //如果下一个节点是会签，则同组的步骤都要撤回
                if (nextNodes.Count == 1 && nextNodes[0].NodeType == WorkNodeType.Sign)
                {
                    await UpdateOtherStepsStatusWithUnWork(currentWorkStep.NodeId, currentWorkStep.GroupId);
                }


                //获取拒绝的步骤（如果指定绝节节点则获取拒绝节点，否则退回上一步的节点，处理人员仍然 是上一步的人员）
                var rejectInfo = await GetRejectInfo(workflowVersion, currentNode, workTask, currentWorkStep, rejectToNodeId);
                
                //如果拒绝返回的节点是开始 节点，则更新流程状态为待审批
                var rejectNodes = rejectInfo.Item2;
                var startNode = rejectNodes.FirstOrDefault(n => n.NodeType == WorkNodeType.Begin);
                if (startNode != null)
                {
                    await CheckAndTaskPendding(workTask, workTaskInfo, startNode, oldWorkTaskStatus);
                }
                else
                {
                    var rejectSteps = rejectInfo.Item1;
                    steps.AddRange(rejectSteps);
                    if (steps.Count == 0)
                        return ProveResult.Failed("找不到可以处理的下一个步骤！");
                }

                await SendTasks(workTask, steps);

                return unitOfWork.Commit(ProveResult.Succeed(steps), ProveResult.Failed("提交失败"));
            }
        }


        /// <summary>
        /// 撤回
        /// 只能撤回未读的记录
        /// </summary>
        /// <param name="workStepId"></param>
        /// <returns></returns>
        public async Task<ProveResult> Withdraw(Guid workStepId, string comment = null)
        {
            await Task.CompletedTask;

            var currentWorkStepInfo = await workStepRepository.GetAsync(workStepId);
            var currentWorkStep = currentWorkStepInfo.ToWorkStep();
            if (currentWorkStep.WorkStepType == WorkStepType.ReadOnly)
                return ProveResult.Failed("只读步骤无法处理！");

            if (!currentWorkStep.IsHandled)
                return ProveResult.Failed("步骤未处理无法撤回！");

            var workTaskInfo = await workTaskRepository.GetAsync(currentWorkStep.WorkTaskId);
            var workTask = workTaskInfo.ToWorkTask();
            var oldWorkTaskStatus = workTask.WorkTaskStatus;
            if (workTask.IsProcessed)
                return ProveResult.Failed("流程已结束无法撤回！");

            var workflowVersion = await workflowStore.GetWorkflowVersion(workTask.WorkflowId.Id, workTask.WorkflowId.VersionId);
            var currentNode = await GetNodeByWorkflowIdAndNodeId(workflowVersion, workTask.WorkflowId, currentWorkStep.NodeId);

            if (currentNode.NodeType == WorkNodeType.End)
                return ProveResult.Failed("已结束无法撤回！");

            var nextNodes = await GetNextNodes(workflowVersion, currentNode, workTask, currentWorkStep);

            var steps = new List<WorkStep>();

            var nextSteps = await workStepRepository.GetListAsync(ws => ws.PreStepGroupId == currentWorkStep.GroupId && ws.HandleType != WorkStepHandleType.UnWork);
            //如果要撤回的节点是转发出去了，则全都要撤回
            if (currentWorkStep.HandleType == WorkStepHandleType.Forward)
            {
                nextSteps.AddRange(await GetForwardSteps(currentWorkStep));
            }


            using (var unitOfWork = unitOfWorkManager.Begin())
            {
                //如果已读则不处理，否则执行撤回||如果下一个节点是会签节点，则允许撤回当前的操作重新审批
                if ((nextSteps.Any() && !nextSteps.Where(s => s.IsRead || s.IsHandled).Any()) || (nextNodes.Count == 1 && nextNodes[0].NodeType == WorkNodeType.Sign))
                {
                    //设置后续节点为未处理
                    var stepInfos = new List<WorkStepInfo>();
                    foreach (var nextStepsInfo in nextSteps)
                    {
                        var nextStep = nextStepsInfo.ToWorkStep();
                        nextStep.Handle(WorkStepHandleType.UnWork, $"撤回：{comment}");
                        stepInfos.Add(nextStep.ToWorkStepInfo(nextStepsInfo));
                    }
                    await workStepRepository.UpdateManyAsync(stepInfos);
                    //设置当前节点为撤回状态
                    //新插入当前步骤
                    var withdrawStep = currentWorkStep.Copy();
                    withdrawStep.Handle(WorkStepHandleType.Withdraw, comment);
                    await workStepRepository.InsertAsync(withdrawStep.ToWorkStepInfo());
                    //新插入当前步骤
                    var newStep = currentWorkStep.Copy();
                    newStep.SetReaded();//对于撤回新插入的记录，它应该是已读的
                    await workStepRepository.InsertAsync(newStep.ToWorkStepInfo());
                    steps.Add(newStep);
                }
                else
                {
                    return ProveResult.Failed("下一步骤已读或已处理，无法撤回！");
                }
                await CheckAndTaskPendding(workTask, workTaskInfo, currentNode, oldWorkTaskStatus);

                if (steps.Count == 0)
                    return ProveResult.Failed("找不到可以处理的下一个步骤！");
                return unitOfWork.Commit(ProveResult.Succeed(steps), ProveResult.Failed("提交失败"));
            }
        }
        /// <summary>
        /// 获取转发出去的步骤id
        /// </summary>
        /// <param name="currentWorkStep"></param>
        /// <returns></returns>
        private async Task<IEnumerable<WorkStepInfo>> GetForwardSteps(WorkStep currentWorkStep)
        {
            return await workStepRepository.GetListAsync(ws => ws.FromForwardStepId == currentWorkStep.Id);
        }

        /// <summary>
        /// 检查并重置流程状态
        /// </summary>
        /// <param name="workTask"></param>
        /// /// <param name="workTaskInfo"></param>
        /// <param name="currentNode"></param>
        /// <returns></returns>
        private async Task CheckAndTaskPendding(WorkTask workTask, WorkTaskInfo workTaskInfo, WorkflowNode currentNode, WorkTaskStatus oldWorkTaskStatus)
        {
            ///如果当前节点是开始节点，则流程状态更新为待处理
            if (currentNode.NodeType == WorkNodeType.Begin)
            {
                workTask.SetPending();
                await workTaskRepository.UpdateAsync(workTask.ToWorkTaskInfo(workTaskInfo));
                await eventManager.PublishAsync(new TaskStateChangeEventData
                {
                    WorkTask = workTask,
                    NewWorkTaskStatus = workTask.WorkTaskStatus,
                });

            }
        }

        /// <summary>
        /// 检查并重置流程状态
        /// </summary>
        /// <param name="workTask"></param>
        /// /// <param name="workTaskInfo"></param>
        /// <param name="currentNode"></param>
        /// <returns></returns>
        private async Task CheckAndSetTaskProcessing(WorkTask workTask, WorkTaskInfo workTaskInfo, WorkflowNode preNode)
        {
            ///如果当前节点是开始节点，则流程状态更新为待处理
            if (preNode.NodeType == WorkNodeType.Begin)
            {
                workTask.SetProcessing();
                await workTaskRepository.UpdateAsync(workTask.ToWorkTaskInfo(workTaskInfo));
                await eventManager.PublishAsync(new TaskStateChangeEventData
                {
                    WorkTask = workTask,
                    OldWorkTaskStatus = WorkTaskStatus.Pending,
                    NewWorkTaskStatus = workTask.WorkTaskStatus,
                });
            }
        }
        /// <summary>
        /// 检查并重置流程状态
        /// </summary>
        /// <param name="workTask"></param>
        /// <param name="workTaskInfo"></param>
        /// <param name="currentNode"></param>
        /// <returns></returns>
        private async Task CheckAndSetTaskProcessed(WorkTask workTask, WorkTaskInfo workTaskInfo, WorkflowNode currentNode)
        {
            ///如果当前节点是结束节点，则流程状态更新为已处理
            if (currentNode.NodeType == WorkNodeType.End)
            {
                workTask.SetProcessed();
                await workTaskRepository.UpdateAsync(workTask.ToWorkTaskInfo(workTaskInfo));

                await eventManager.PublishAsync(new TaskFinishedEventData
                {
                    WorkTask = workTask
                });

                //已结束时，将其他的步骤设为未处理
                var steps = await workStepRepository.GetListAsync(s => s.WorkTaskId == workTask.Id && s.IsHandled == false);
                foreach (var stepInfo in steps)
                {
                    var step = stepInfo.ToWorkStep();
                    step.Handle(WorkStepHandleType.UnWork);
                    await workStepRepository.UpdateAsync(step.ToWorkStepInfo(stepInfo));
                }
                await workStepRepository.UpdateManyAsync(steps);

                await eventManager.PublishAsync(new TaskStateChangeEventData
                {
                    WorkTask = workTask,
                    OldWorkTaskStatus = WorkTaskStatus.Processing,
                    NewWorkTaskStatus = workTask.WorkTaskStatus,
                });
            }
        }

        /// <summary>
        /// 转发
        /// </summary>
        /// <param name="workStepId"></param>
        /// <param name="userSelectors">转发的目标成员</param>
        /// <param name="comment"></param>
        /// <returns></returns>
        public async Task<ProveResult> Forward(Guid workStepId, List<NodeUser> userSelectors,List<User> users, string comment = null)
        {

            await Task.CompletedTask;

            if ((userSelectors == null || userSelectors.Count == 0) && (users == null || users.Count == 0))
                return ProveResult.Failed("未提供转办的用户或转办用户无效！"); ;

            var currentWorkStepInfo = await workStepRepository.GetAsync(workStepId);
            var currentWorkStep = currentWorkStepInfo.ToWorkStep();
            var workTaskInfo = await workTaskRepository.GetAsync(currentWorkStep.WorkTaskId);
            var workTask = workTaskInfo.ToWorkTask();
            var steps = new List<WorkStep>();


            //设置当前节点为转发状态
            using (var unitOfWork = unitOfWorkManager.Begin())
            {
                currentWorkStep.Handle(WorkStepHandleType.Forward, comment);
                await workStepRepository.UpdateAsync(currentWorkStep.ToWorkStepInfo(currentWorkStepInfo));
                //插入新处理人的处理步骤
                //遍历用户 选择器获取实际用户 并转发处理

                //优先选择用户
                if(users!=null && users.Count>0)
                {
                    users.ForEach(user =>
                    {
                        var newStep = currentWorkStep.Copy();
                        newStep.SetHandleUser(user);
                        newStep.FromForward(currentWorkStep.Id);
                        workStepRepository.InsertAsync(newStep.ToWorkStepInfo());
                        steps.Add(newStep);
                    });
                }
                else
                {
                    foreach (var selector in userSelectors)
                    {
                        var userSelector = userSelectorManager.GetUserSelector(selector.SelectorId);
                        foreach (var section in selector.Selections)
                        {
                            var _users = userSelector.GetUsers(new SelectorInput
                            {
                                SelectionId = section.Id,
                                Expression = selector.Parameter,
                                WorkTask = workTask
                            });

                            _users.ForEach(user =>
                            {
                                var newStep = currentWorkStep.Copy();
                                newStep.SetHandleUser(user);
                                newStep.FromForward(currentWorkStep.Id);
                                workStepRepository.InsertAsync(newStep.ToWorkStepInfo());
                                steps.Add(newStep);
                            });
                        }
                    }
                }
                if (steps.Count == 0)
                    return ProveResult.Failed("找不到可以处理的下一个步骤！");
                return unitOfWork.Commit(ProveResult.Succeed(steps), ProveResult.Failed("提交失败"));
            }
        }

        /// <summary>
        /// 获取正在处理的会签任务
        /// </summary>
        /// <param name="currentNodeId"></param>
        /// <param name="stepGroupId"></param>
        /// <returns></returns>
        private async Task<long> GetOnHandingSignStepsCount(Guid currentNodeId, string stepGroupId)
        {
            await Task.CompletedTask;

            var steps = await workStepRepository.GetCountAsync(ws => ws.GroupId == stepGroupId && ws.IsHandled == false && ws.NodeId != currentNodeId);
            return steps;
        }

        /// <summary>
        /// 获取审批步骤
        /// </summary>
        /// <param name="fromNodeId"></param>
        /// <param name="fromNodeName"></param>
        /// <param name="workTask"></param>
        /// <param name="node"></param>
        /// <param name="preStepGroupId">上一步骤分组id</param>
        /// <param name="nextStepGroupId">下一步骤分组id</param>
        /// <returns></returns>
        private List<WorkStep> GetApproveSteps(Guid fromNodeId, string fromNodeName, WorkTask workTask, WorkflowNode node, string preStepGroupId, string nextStepGroupId)
        {
            List<WorkStep> steps = new List<WorkStep>();
            var nodeUsers = node.GetHandleUsers(workTask, userSelectorManager);

            foreach (var nodeUser in nodeUsers)
            {
                foreach (var user in nodeUser.Value)
                {
                    steps.Add(new WorkStep(Guid.NewGuid(), workTask.Id, fromNodeId, fromNodeName, node.Id, node.Name, user, nodeUser.Key == NodeUser.NodeHandleType.Handle ? WorkStepType.Handle : WorkStepType.ReadOnly, nextStepGroupId, preStepGroupId));
                }
            }
            return steps;
        }
        /// <summary>
        /// 根据选择器获取审批用户
        /// </summary>
        /// <param name="userSelectors"></param>
        /// <param name="workTask"></param>
        /// <param name="userHandler"></param>
        private void GetUsersByUserSelectors(List<NodeUser> userSelectors, WorkTask workTask, Action<User> userHandler)
        {
            GetUsersByUserSelectors(userSelectors, workTask, (selector, user) => userHandler?.Invoke(user));
        }
        /// <summary>
        /// 根据选择器获取审批用户
        /// </summary>
        /// <param name="userSelectors"></param>
        /// <param name="workTask"></param>
        /// <param name="userHandler"></param>
        private void GetUsersByUserSelectors(List<NodeUser> userSelectors, WorkTask workTask, Action<NodeUser, User> userHandler)
        {
            foreach (var selector in userSelectors)
            {
                var userSelector = userSelectorManager.GetUserSelector(selector.SelectorId);
                foreach (var selection in selector.Selections)
                {
                    var _users = userSelector.GetUsers(new SelectorInput
                    {
                        SelectionId = selection.Id,
                        Expression = selector.Parameter,
                        WorkTask = workTask
                    });

                    foreach (var user in _users)
                    {
                        userHandler?.Invoke(selector, user);
                    }

                }
            }
        }



        /// <summary>
        /// 分配任务到处理人员
        /// </summary>
        /// <param name="workTask"></param>
        /// <param name="workSteps"></param>
        /// <returns></returns>
        private async Task SendTasks(WorkTask workTask, List<WorkStep> workSteps)
        {

            foreach (var item in workSteps)
            {
                item.IsHandled = false;
                await workStepRepository.InsertAsync(item.ToWorkStepInfo());
                //TODO 发布开启任务事件
                //TODO 发布开启消息
                //TODO 考虑增加让步骤保存每次处理的表单信息
            }
            await eventManager.PublishAsync(new SendTaskEventData
            {
                WorkTask = workTask,
                WorkSteps = workSteps
            });
        }


        /// <summary>
        /// 清除模拟 记录
        /// </summary>
        /// <returns></returns>
        public async Task ClearSimulationRecord()
        {
            var worktasks = await workTaskRepository.GetListAsync(wt => wt.Name == "模拟流程");
            var worktaskIds = worktasks.ToList().Select(wt => wt.Id);
            using (var unitOfWork = unitOfWorkManager.Begin())
            {
                await workStepRepository.DeleteManyAsync(ws => worktaskIds.Contains(ws.WorkTaskId));
                await workTaskRepository.DeleteManyAsync(wt => worktaskIds.Contains(wt.Id));
                await unitOfWork.CompleteAsync();
            }
        }



        /// <summary>
        /// 获取流程所有过程
        /// </summary>
        /// <param name="user"></param>
        /// <returns></returns>
        public async Task<List<WorkStep>> GetAllTaskStepsOfWorkTaskAsync(Guid workTaskId)
        {
            await Task.CompletedTask;
            return (await workStepRepository.GetListAsync(ws => ws.WorkTaskId == workTaskId)).OrderByDescending(ws => ws.CreationTime).Select(s => s.ToWorkStep()).ToList();
        }

        /// <summary>
        /// 获取流程所有过程
        /// </summary>
        /// <param name="user"></param>
        /// <returns></returns>
        public async Task<List<WorkStep>> GetAllTaskStepsOfWorkTaskByEntityInfoAsync(string entityFullName, string entityKeyValue)
        {
            var worktasks = await workTaskRepository.GetListAsync(t => t.EntityFullName == entityFullName && t.EntityKeyValue == entityKeyValue);
            return (await workStepRepository.GetListAsync(ws => worktasks.Select(w => w.Id).Contains(ws.WorkTaskId))).OrderByDescending(ws => ws.CreationTime).Select(s => s.ToWorkStep()).ToList();
        }

        /// <summary>
        /// 获取流程信息
        /// </summary>
        /// <param name="user"></param>
        /// <returns></returns>
        public async Task<WorkTask> GetWorkTaskAsync(Guid workTaskId)
        {
            return (await workTaskRepository.GetAsync(workTaskId)).ToWorkTask();
        }


        /// <summary>
        /// 获取用户所有的流程任务
        /// </summary>
        /// <param name="user"></param>
        /// <returns></returns>
        public async Task<PageResult<WorkTask>> GetAllTasksOfUserAsync(string userId, int pageIndex = 1, int pageSize = -1)
        {
            return await workTaskRepository.GetAllTasksOfUserAsync(userId, pageIndex, pageSize);

        }


        /// <summary>
        /// 获取用户已处理的流程任务
        /// </summary>
        /// <param name="user"></param>
        /// <returns></returns>
        public async Task<PageResult<WorkTask>> GetWorkflowedTasksOfUserAsync(string userId, int pageIndex = 1, int pageSize = -1)
        {
            return await workTaskRepository.GetWorkflowedTasksOfUserAsync(userId, pageIndex, pageSize);
        }

        /// <summary>
        /// 获取用户未处理的流程任务
        /// </summary>
        /// <param name="user"></param>
        /// <returns></returns>
        public async Task<PageResult<WorkTask>> GetUnHandledWorkTasksOfUserAsync(string userId, int pageIndex = 1, int pageSize = -1)
        {
            return await workTaskRepository.GetUnHandledWorkTasksOfUserAsync(userId, pageIndex, pageSize);
        }

        /// <summary>
        /// 获取用户处理过的流程任务
        /// </summary>
        /// <param name="user"></param>
        /// <returns></returns>
        public async Task<PageResult<WorkTask>> GetHandledWorkTasksOfUserAsync(string userId, int pageIndex = 1, int pageSize = -1)
        {
            return await workTaskRepository.GetHandledWorkTasksOfUserAsync(userId, pageIndex, pageSize);
        }


        /// <summary>
        /// 用户发起的流程
        /// </summary>
        /// <param name="user"></param>
        /// <returns></returns>
        public async Task<PageResult<WorkTask>> GetTasksOfStartUserAsync(string userId, int pageIndex = 1, int pageSize = -1)
        {
            return await workTaskRepository.GetTasksOfStartUserAsync(userId, pageIndex, pageSize);
        }


        /// <summary>
        /// 获取选择器源数据,可提供前台选择
        /// </summary>
        /// <param name="selectorId"></param>
        /// <returns></returns>
        public async Task<List<Selection>> GetUserSelectionsOfUserSelector(string selectorId)
        {
            await Task.CompletedTask;
            if (string.IsNullOrEmpty(selectorId)) return new List<Selection>();
            var userSelector = userSelectorManager.GetUserSelector(selectorId);
            return userSelector.GetSelections();
        }


        /// <summary>
        /// 删除流程
        /// 同时删除审批记录
        /// </summary>
        /// <param name="worktaskId"></param>
        /// <returns></returns>
        public async Task DeleteWorkTask(Guid worktaskId)
        {
            var worktaskInfo = await workTaskRepository.GetAsync(worktaskId);

            if (worktaskInfo == null)
                throw new Exception($"查无此项:{worktaskId}");

            var worktask = worktaskInfo.ToWorkTask();

            if (!worktask.IsPending && worktask.WorkTaskStatus != WorkTaskStatus.Canceled)
                throw new Exception("非待审批状态无法删除");

            using (var unitOfWork = unitOfWorkManager.Begin())
            {
                await workStepRepository.DeleteManyAsync(ws => ws.WorkTaskId == worktaskId);
                await workTaskRepository.DeleteAsync(worktaskId);
                await unitOfWork.CompleteAsync();
            }
        }
        /// <summary>
        /// 获取驳回节点信息
        /// </summary>
        /// <param name="workStepId"></param>
        /// <returns></returns>
        public async Task<List<WorkflowNode>> GetRejectNodes(Guid workStepId)
        {
            var currentWorkStepInfo = await workStepRepository.GetAsync(workStepId);
            var currentWorkStep = currentWorkStepInfo.ToWorkStep();
            var workTaskInfo = await workTaskRepository.GetAsync(currentWorkStep.WorkTaskId);
            var workTask = workTaskInfo.ToWorkTask();
            var workflowVersion = await workflowStore.GetWorkflowVersion(workTask.WorkflowId.Id, workTask.WorkflowId.VersionId);
            var currentNode = await GetNodeByWorkflowIdAndNodeId(workflowVersion, workTask.WorkflowId, currentWorkStep.NodeId);
            var rejectInfo = await GetRejectNodes(workflowVersion, currentNode, workTask, currentWorkStep);
            return rejectInfo;
        }

        #endregion

        public async Task ClearSimulationWorkTasks()
        {
            //自动清理一天前的
            var beforeTime = DateTime.Now.AddDays(-1);
            var workTaskInfos = await workTaskRepository.GetListAsync(v => v.Deleted == false && v.IsSimulation == true && v.CreationTime < beforeTime);
            await workTaskRepository.DeleteManyAsync(workTaskInfos.Select(wt => wt.Id));
        }

        /// <summary>
        /// 自动处理同层级用户的其它审批步骤
        /// </summary>
        /// <param name="handleUser"></param>
        /// <param name="groupId"></param>
        /// <param name="comment"></param>
        /// <returns></returns>
        private async Task AutoHandleSameGroupOfUser(Guid stepId, User handleUser, string groupId)
        {
            var currentWorkStepInfos = await workStepRepository.GetListAsync(s => s.IsHandled == false && s.Id != stepId && s.HandleUser_Id == handleUser.Id && s.GroupId == groupId);
            var currentWorkSteps = currentWorkStepInfos.Select(s => s.ToWorkStep()).ToList();
            if (currentWorkSteps.Count > 0)
                await eventManager.PublishAsync(new AutoHandleStepsEventData() { Steps = currentWorkSteps, Comment = "自动处理" });

        }

        /// <summary>
        /// 自动处理下级用户的其它审批步骤
        /// </summary>
        /// <param name="handleUser"></param>
        /// <param name="steps"></param>
        /// <returns></returns>
        private async Task AutoHandleNextGroupOfUser(WorkflowVersion workflowVersion, List<WorkStep> steps, User handleUser)
        {
            steps.ForEach(async step =>
            {
                var handlerUserId = step?.HandleUser?.Id;
                var count = await workStepRepository.GetCountAsync(s => s.IsHandled == true && s.HandleType == WorkStepHandleType.Pass && s.HandleUser_Id == handlerUserId && s.HandleUser_Id == handleUser.Id  && s.GroupId == step.PreStepGroupId);

                var node = workflowVersion.AllNodes.Where(n => n.Id == step.NodeId).FirstOrDefault();
                if (count > 0)
                {
                    await eventManager.PublishAsync(new AutoHandleStepsEventData() { Steps = new List<WorkStep> { step }, Comment = "用户前一步已审批通过，自动处理" });
                }

            });
        }
    }
}
